package com.itheima.Wuziqi.ui;

import com.itheima.Wuziqi.dao.UserDatabase;
import com.itheima.Wuziqi.dao.UserDatabaseInFile;
import com.itheima.Wuziqi.entity.AIPlayer;
import com.itheima.Wuziqi.entity.HumanPlayer;
import com.itheima.Wuziqi.entity.Player;
import com.itheima.Wuziqi.entity.User;
import com.itheima.Wuziqi.service.*;

import javax.swing.*;
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;

/**
 * 游戏主界面
 */
public class MainFrame extends JFrame implements GameListener {
    private static final int BOARD_SIZE = 15;
    private static final int CELL_SIZE = 40;
    private static final int MARGIN = 30;
    private static final int PIECE_SIZE = 30;
    
    private GameController gameController;
    private ChessboardPanel chessboardPanel;
    private User currentUser;
    private UserDatabase userDatabase;
    private JLabel statusLabel;
    private AIPlayer aiPlayer;

    private JLabel usernameLabel;
    private JLabel winCountLabel;
    private JLabel loseCountLabel;
    private JLabel drawCountLabel;
    
    public MainFrame() {
        // 初始化用户数据库
        this.userDatabase = new UserDatabaseInFile("users.dat");
        
        // 初始化游戏组件
        Board board = new Chessboard(BOARD_SIZE);
        GameRule rule = new GobangRule(BOARD_SIZE);
        this.gameController = new GameController(board, rule, userDatabase);
        this.gameController.addGameListener(this);
        
        // 创建AI玩家
        this.aiPlayer = new AIPlayer(Player.WHITE, 2); // 默认中等难度
        
        initUI();
        
        setTitle("五子棋");
        setSize(CELL_SIZE * BOARD_SIZE + MARGIN * 2 + 200, // 额外空间用于信息面板
                CELL_SIZE * BOARD_SIZE + MARGIN * 2 + 50);
        setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        setLocationRelativeTo(null);
        setResizable(false);
    }
    
    private void initUI() {
        // 创建主面板，使用BorderLayout
        JPanel mainPanel = new JPanel(new BorderLayout());
        
        // 创建棋盘面板
        chessboardPanel = new ChessboardPanel();
        mainPanel.add(chessboardPanel, BorderLayout.CENTER);

        // 添加鼠标监听器
        chessboardPanel.addMouseListener(new MouseAdapter() {
            @Override
            public void mouseClicked(MouseEvent e) {
                // 检查游戏是否已正确初始化
                if (gameController.getCurrentPlayer() == null) {
                    JOptionPane.showMessageDialog(MainFrame.this,
                            "请先开始游戏！", "提示", JOptionPane.WARNING_MESSAGE);
                    return;
                }

                if (gameController.isGameOver()) return;

                // 计算落子位置
                int x = e.getX() - MARGIN + CELL_SIZE / 2;
                int y = e.getY() - MARGIN + CELL_SIZE / 2;
                int row = y / CELL_SIZE;
                int col = x / CELL_SIZE;

                // 人类玩家落子
                gameController.makeMove(new java.awt.Point(col, row));
            }
        });
        
        // 创建右侧信息面板
        JPanel infoPanel = new JPanel(new BorderLayout());
        infoPanel.setPreferredSize(new Dimension(200, 0));
        infoPanel.setBorder(BorderFactory.createEmptyBorder(20, 10, 20, 10));

        // 用户信息
        JPanel userInfoPanel = new JPanel(new GridBagLayout());
        userInfoPanel.setBorder(BorderFactory.createTitledBorder("用户信息"));
        GridBagConstraints gbc = new GridBagConstraints();
        gbc.insets = new Insets(5, 5, 5, 5);
        gbc.anchor = GridBagConstraints.WEST;
        gbc.gridx = 0;
        gbc.gridy = 0;

        JLabel nameLabel = new JLabel("用户名: ");
        userInfoPanel.add(nameLabel, gbc);

        gbc.gridx = 1;
        this.usernameLabel = new JLabel("未登录");
        userInfoPanel.add(this.usernameLabel, gbc);

        gbc.gridx = 0;
        gbc.gridy++;
        JLabel winLabel = new JLabel("胜场: ");
        userInfoPanel.add(winLabel, gbc);

        gbc.gridx = 1;
        this.winCountLabel = new JLabel("0");
        userInfoPanel.add(this.winCountLabel, gbc);

        gbc.gridx = 0;
        gbc.gridy++;
        JLabel loseLabel = new JLabel("负场: ");
        userInfoPanel.add(loseLabel, gbc);

        gbc.gridx = 1;
        this.loseCountLabel = new JLabel("0");
        userInfoPanel.add(this.loseCountLabel, gbc);

        gbc.gridx = 0;
        gbc.gridy++;
        JLabel drawLabel = new JLabel("平局: ");
        userInfoPanel.add(drawLabel, gbc);

        gbc.gridx = 1;
        this.drawCountLabel = new JLabel("0");
        userInfoPanel.add(this.drawCountLabel, gbc);
        
        // 状态信息
        JPanel statusPanel = new JPanel(new FlowLayout(FlowLayout.CENTER));
        statusPanel.setBorder(BorderFactory.createTitledBorder("游戏状态"));
        statusLabel = new JLabel("请开始新游戏");
        statusPanel.add(statusLabel);
        
        // 游戏控制按钮
        JPanel controlPanel = new JPanel(new GridLayout(4, 1, 5, 5));
        controlPanel.setBorder(BorderFactory.createTitledBorder("游戏控制"));
        
        JButton startHvHButton = new JButton("人人对战");
        startHvHButton.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent e) {
                startHumanVsHumanGame();
            }
        });
        
        JButton startHvAButton = new JButton("人机对战");
        startHvAButton.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent e) {
                startHumanVsAIGame();
            }
        });
        
        JButton changeDifficultyButton = new JButton("调整AI难度");
        changeDifficultyButton.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent e) {
                changeAIDifficulty();
            }
        });
        
        JButton logoutButton = new JButton("退出登录");
        logoutButton.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent e) {
                logout();
            }
        });
        
        controlPanel.add(startHvHButton);
        controlPanel.add(startHvAButton);
        controlPanel.add(changeDifficultyButton);
        controlPanel.add(logoutButton);
        
        // 添加到信息面板
        infoPanel.add(userInfoPanel, BorderLayout.NORTH);
        infoPanel.add(statusPanel, BorderLayout.CENTER);
        infoPanel.add(controlPanel, BorderLayout.SOUTH);
        
        mainPanel.add(infoPanel, BorderLayout.EAST);
        
        add(mainPanel);
    }

    // 开始人人对战
    private void startHumanVsHumanGame() {
        if (currentUser == null) {
            JOptionPane.showMessageDialog(this, "请先登录！", "提示", JOptionPane.WARNING_MESSAGE);
            return;
        }

        String player2Name = JOptionPane.showInputDialog(this, "请输入对手用户名:", "输入对手信息", JOptionPane.PLAIN_MESSAGE);
        if (player2Name == null || player2Name.trim().isEmpty()) {
            player2Name = "玩家2";
        }

        Player player1 = new HumanPlayer(Player.BLACK, currentUser.getUsername());
        Player player2 = new HumanPlayer(Player.WHITE, player2Name);

        gameController.setPlayers(player1, player2);
        gameController.startNewGame();
    }

    // 开始人机对战
    private void startHumanVsAIGame() {
        if (currentUser == null) {
            JOptionPane.showMessageDialog(this, "请先登录！", "提示", JOptionPane.WARNING_MESSAGE);
            return;
        }

        Player player1 = new HumanPlayer(Player.BLACK, currentUser.getUsername());
        gameController.setPlayers(player1, aiPlayer);
        gameController.startNewGame();
    }
    
    // 调整AI难度
    private void changeAIDifficulty() {
        String[] options = {"简单", "中等", "困难"};
        int choice = JOptionPane.showOptionDialog(this, "选择AI难度:", "调整难度",
                JOptionPane.DEFAULT_OPTION, JOptionPane.PLAIN_MESSAGE, null, options, options[1]);
        
        if (choice != -1) {
            aiPlayer.setDifficulty(choice + 1);
            JOptionPane.showMessageDialog(this, "AI难度已设置为: " + options[choice], 
                    "设置成功", JOptionPane.INFORMATION_MESSAGE);
        }
    }
    
    // 退出登录
    private void logout() {
        int confirm = JOptionPane.showConfirmDialog(this, "确定要退出登录吗?", "确认", JOptionPane.YES_NO_OPTION);
        if (confirm == JOptionPane.YES_OPTION) {
            LoginFrame loginFrame = new LoginFrame(userDatabase, this);
            loginFrame.setVisible(true);
            dispose();
        }
    }
    
    // 游戏结束后显示选项
    private void showGameOverOptions(String message) {
        String[] options = {"再来一局", "退出游戏"};
        int choice = JOptionPane.showOptionDialog(this, message, "游戏结束",
                JOptionPane.DEFAULT_OPTION, JOptionPane.PLAIN_MESSAGE, null, options, options[0]);
        
        if (choice == 0) {
            // 再来一局，保持当前游戏模式
            gameController.startNewGame();
        } else if (choice == 1) {
            // 退出游戏，返回主界面
            // 这里可以添加返回主界面的逻辑
        }
    }
    
    public void setCurrentUser(User user) {
        this.currentUser = user;
        gameController.setCurrentUser(user);
        
        // 更新用户信息显示
        Component[] components = ((JPanel)((JPanel)getContentPane().getComponent(0)).getComponent(1)).getComponent(0).getParent().getComponents();
//        if (components.length >= 8 && user != null) {
//            ((JLabel)components[1]).setText(user.getUsername());
//            ((JLabel)components[3]).setText(String.valueOf(user.getWinCount()));
//            ((JLabel)components[5]).setText(String.valueOf(user.getLoseCount()));
//            ((JLabel)components[7]).setText(String.valueOf(user.getDrawCount()));
//        }
        if (user != null) {
            usernameLabel.setText(user.getUsername());
            winCountLabel.setText(String.valueOf(user.getWinCount()));
            loseCountLabel.setText(String.valueOf(user.getLoseCount()));
            drawCountLabel.setText(String.valueOf(user.getDrawCount()));
        } else {
            usernameLabel.setText("未登录");
            winCountLabel.setText("0");
            loseCountLabel.setText("0");
            drawCountLabel.setText("0");
        }
    }

    /**
     * 刷新用户信息显示
     */
    private void refreshUserInfoDisplay() {
        if (currentUser != null) {
            usernameLabel.setText(currentUser.getUsername());
            winCountLabel.setText(String.valueOf(currentUser.getWinCount()));
            loseCountLabel.setText(String.valueOf(currentUser.getLoseCount()));
            drawCountLabel.setText(String.valueOf(currentUser.getDrawCount()));
        } else {
            usernameLabel.setText("未登录");
            winCountLabel.setText("0");
            loseCountLabel.setText("0");
            drawCountLabel.setText("0");
        }
    }
    
    // 棋盘面板内部类
    class ChessboardPanel extends JPanel {
        @Override
        protected void paintComponent(Graphics g) {
            super.paintComponent(g);
            
            // 设置背景色为木色
            setBackground(new Color(222, 184, 135));
            
            // 绘制棋盘网格
            g.setColor(Color.BLACK);
            for (int i = 0; i < BOARD_SIZE; i++) {
                // 横线
                g.drawLine(MARGIN, MARGIN + i * CELL_SIZE,
                        MARGIN + (BOARD_SIZE - 1) * CELL_SIZE, MARGIN + i * CELL_SIZE);
                // 竖线
                g.drawLine(MARGIN + i * CELL_SIZE, MARGIN,
                        MARGIN + i * CELL_SIZE, MARGIN + (BOARD_SIZE - 1) * CELL_SIZE);
            }
            
            // 绘制天元和星位
            int[] stars = {3, 7, 11};
            for (int x : stars) {
                for (int y : stars) {
                    g.fillOval(MARGIN + x * CELL_SIZE - 3, MARGIN + y * CELL_SIZE - 3, 6, 6);
                }
            }
            
            // 绘制棋子
            int[][] boardState = gameController.getBoard().getBoardState();
            for (int i = 0; i < BOARD_SIZE; i++) {
                for (int j = 0; j < BOARD_SIZE; j++) {
                    if (boardState[i][j] == Player.BLACK) { // 黑棋
                        g.setColor(Color.BLACK);
                        g.fillOval(MARGIN + j * CELL_SIZE - PIECE_SIZE / 2,
                                MARGIN + i * CELL_SIZE - PIECE_SIZE / 2,
                                PIECE_SIZE, PIECE_SIZE);
                    } else if (boardState[i][j] == Player.WHITE) { // 白棋
                        g.setColor(Color.WHITE);
                        g.fillOval(MARGIN + j * CELL_SIZE - PIECE_SIZE / 2,
                                MARGIN + i * CELL_SIZE - PIECE_SIZE / 2,
                                PIECE_SIZE, PIECE_SIZE);
                        g.setColor(Color.BLACK);
                        g.drawOval(MARGIN + j * CELL_SIZE - PIECE_SIZE / 2,
                                MARGIN + i * CELL_SIZE - PIECE_SIZE / 2,
                                PIECE_SIZE, PIECE_SIZE);
                    }
                }
            }
        }
    }
    
    // 游戏监听器方法
    @Override
    public void gameStarted() {
        statusLabel.setText("游戏开始! " + gameController.getCurrentPlayer().getName() + " 先行");
        chessboardPanel.repaint();
    }
    
    @Override
    public void piecePlaced(int row, int col, int playerType) {
        chessboardPanel.repaint();
    }
    
    @Override
    public void gameWon(Player winner) {
        String message = winner.getName() + " 获胜!";
        statusLabel.setText(message);
        // 从数据库重新加载用户数据以获取最新的统计信息
        if (currentUser != null) {
            User updatedUser = userDatabase.queryByUserId(currentUser.getUsername());
            if (updatedUser != null) {
                this.currentUser = updatedUser;
                refreshUserInfoDisplay();
            }
        }
        showGameOverOptions(message);
    }
    
    @Override
    public void gameDrawn() {
        String message = "游戏平局!";
        statusLabel.setText(message);

        // 从数据库重新加载用户数据以获取最新的统计信息
        if (currentUser != null) {
            User updatedUser = userDatabase.queryByUserId(currentUser.getUsername());
            if (updatedUser != null) {
                this.currentUser = updatedUser;
                refreshUserInfoDisplay();
            }
        }
        showGameOverOptions(message);
    }
    
    @Override
    public void playerChanged(Player newPlayer) {
        statusLabel.setText("轮到 " + newPlayer.getName() + " 落子");
    }
}
    